package com.team9.fitness.service;

import com.team9.fitness.entity.UserAvatar;
import com.team9.fitness.mapper.UserAvatarMapper;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.time.LocalDateTime;
import java.util.List;
import java.util.UUID;

/**
 * 用户头像服务
 */
@Slf4j
@Service
@RequiredArgsConstructor
public class UserAvatarService {

    private final UserAvatarMapper userAvatarMapper;
    
    // 头像存储路径
    private static final String AVATAR_UPLOAD_PATH = "uploads/avatars/";
    
    // 允许的文件类型
    private static final String[] ALLOWED_MIME_TYPES = {
        "image/jpeg", "image/png", "image/gif", "image/webp"
    };
    
    // 最大文件大小 (5MB)
    private static final long MAX_FILE_SIZE = 5 * 1024 * 1024;

    /**
     * 上传头像（通过Base64数据）
     */
    public UserAvatar uploadAvatarFromBase64(Long userId, String fileName, String contentType, 
                                            Long fileSize, String base64Data) throws IOException {
        log.info("开始上传头像 - userId: {}, fileName: {}, contentType: {}, fileSize: {}", userId, fileName, contentType, fileSize);
        log.info("Base64数据长度: {}", base64Data != null ? base64Data.length() : 0);
        
        // 验证文件大小
        if (fileSize > MAX_FILE_SIZE) {
            log.error("文件大小超过限制: {} > {}", fileSize, MAX_FILE_SIZE);
            throw new IllegalArgumentException("文件大小不能超过5MB");
        }
        
        // 验证文件类型
        boolean isValidType = false;
        for (String allowedType : ALLOWED_MIME_TYPES) {
            if (allowedType.equals(contentType)) {
                isValidType = true;
                break;
            }
        }
        if (!isValidType) {
            log.error("不支持的文件类型: {}, 支持的类型: {}", contentType, String.join(", ", ALLOWED_MIME_TYPES));
            throw new IllegalArgumentException("不支持的文件类型，只支持: " + String.join(", ", ALLOWED_MIME_TYPES));
        }
        
        // 创建存储目录
        Path uploadPath = Paths.get(System.getProperty("user.dir"), AVATAR_UPLOAD_PATH);
        log.info("上传路径: {}", uploadPath.toString());
        if (!Files.exists(uploadPath)) {
            log.info("创建上传目录: {}", uploadPath.toString());
            Files.createDirectories(uploadPath);
        }
        
        // 生成文件名
        String fileExtension = getFileExtension(fileName);
        String newFileName = String.format("avatar_%d_%s.%s", userId, UUID.randomUUID().toString(), fileExtension);
        log.info("生成的文件名: {}", newFileName);
        
        // 解码Base64数据并保存文件
        try {
            log.info("开始解码Base64数据");
            byte[] fileBytes = java.util.Base64.getDecoder().decode(base64Data);
            log.info("Base64解码成功，文件字节数: {}", fileBytes.length);
            
            Path filePath = uploadPath.resolve(newFileName);
            log.info("保存文件到: {}", filePath.toString());
            Files.write(filePath, fileBytes);
            log.info("文件保存成功: {}", filePath.toString());
        } catch (Exception e) {
            log.error("Base64解码或文件保存失败: {}", e.getMessage(), e);
            throw new IOException("文件保存失败: " + e.getMessage());
        }
        
        // 将之前的头像设为非激活
        log.info("将用户 {} 的旧头像设为非激活", userId);
        userAvatarMapper.deactivateAllByUserId(userId);
        
        // 创建头像记录
        UserAvatar userAvatar = UserAvatar.builder()
            .userId(userId)
            .avatarUrl("/uploads/avatars/" + newFileName)
            .fileName(newFileName)
            .fileSize(fileSize)
            .mimeType(contentType)
            .uploadTime(LocalDateTime.now())
            .isActive(true)
            .createdAt(LocalDateTime.now())
            .updatedAt(LocalDateTime.now())
            .build();
        
        log.info("保存头像记录到数据库: {}", userAvatar);
        userAvatarMapper.insert(userAvatar);
        
        log.info("头像上传成功 - userId: {}, avatarUrl: {}", userId, userAvatar.getAvatarUrl());
        return userAvatar;
    }

    /**
     * 获取用户激活的头像
     */
    public UserAvatar getActiveAvatar(Long userId) {
        return userAvatarMapper.findByUserIdAndActive(userId);
    }

    /**
     * 获取用户所有头像
     */
    public List<UserAvatar> getUserAvatars(Long userId) {
        return userAvatarMapper.findByUserId(userId);
    }

    /**
     * 删除头像
     */
    public boolean deleteAvatar(Long userId) {
        UserAvatar avatar = userAvatarMapper.findByUserIdAndActive(userId);
        if (avatar != null) {
            // 删除文件
            try {
                Path filePath = Paths.get(System.getProperty("user.dir"), AVATAR_UPLOAD_PATH, avatar.getFileName());
                Files.deleteIfExists(filePath);
            } catch (IOException e) {
                log.error("删除头像文件失败: {}", e.getMessage());
            }
            
            // 删除数据库记录
            int result = userAvatarMapper.deleteById(avatar.getId());
            return result > 0;
        }
        return false;
    }

    /**
     * 清理非激活头像
     */
    public int cleanInactiveAvatars() {
        return userAvatarMapper.cleanInactiveAvatars();
    }

    /**
     * 验证文件
     */
    private void validateFile(MultipartFile file) {
        if (file.isEmpty()) {
            throw new IllegalArgumentException("文件不能为空");
        }
        
        if (file.getSize() > MAX_FILE_SIZE) {
            throw new IllegalArgumentException("文件大小不能超过5MB");
        }
        
        String contentType = file.getContentType();
        boolean isValidType = false;
        for (String allowedType : ALLOWED_MIME_TYPES) {
            if (allowedType.equals(contentType)) {
                isValidType = true;
                break;
            }
        }
        
        if (!isValidType) {
            throw new IllegalArgumentException("不支持的文件类型，只支持: " + String.join(", ", ALLOWED_MIME_TYPES));
        }
    }

    /**
     * 获取文件扩展名
     */
    private String getFileExtension(String fileName) {
        if (fileName == null || !fileName.contains(".")) {
            return "jpg";
        }
        return fileName.substring(fileName.lastIndexOf(".") + 1).toLowerCase();
    }
}
